home *** CD-ROM | disk | FTP | other *** search
/ Mastering Internet Develo…oft ActiveX Technologies / Mastering Internet Development with ActiveX (1996)(Microsoft).iso / labs / lab10.2 / final / echo.cpp next >
C/C++ Source or Header  |  1996-07-16  |  7KB  |  226 lines

  1. // ECHO.CPP - Implementation file for your Internet Server
  2. //    Echo ISAPI App
  3.  
  4. #include <afx.h>
  5. #include <afxwin.h>
  6. #include <afxisapi.h>
  7. #include "resource.h"
  8. #include "Echo.h"
  9.  
  10. ///////////////////////////////////////////////////////////////////////
  11. // command-parsing map
  12.  
  13. BEGIN_PARSE_MAP(CEchoExtension, CHttpServer)
  14.     // TODO: insert your ON_PARSE_COMMAND() and 
  15.     // ON_PARSE_COMMAND_PARAMS() here to hook up your commands.
  16.     // For example:
  17.     
  18.     //Lab 10.2, ex 2 - Implementing Echo
  19.     ON_PARSE_COMMAND(EchoRequest, CEchoExtension, ITS_PSTR)
  20.     ON_PARSE_COMMAND_PARAMS("option=full")
  21.  
  22.     ON_PARSE_COMMAND(Default, CEchoExtension, ITS_EMPTY)
  23.     DEFAULT_PARSE_COMMAND(Default, CEchoExtension)
  24. END_PARSE_MAP(CEchoExtension)
  25.  
  26.  
  27. ///////////////////////////////////////////////////////////////////////
  28. // The one and only CEchoExtension object
  29.  
  30. CEchoExtension theExtension;
  31.  
  32.  
  33. ///////////////////////////////////////////////////////////////////////
  34. // CEchoExtension implementation
  35.  
  36. CEchoExtension::CEchoExtension()
  37. {
  38. }
  39.  
  40. CEchoExtension::~CEchoExtension()
  41. {
  42. }
  43.  
  44. BOOL CEchoExtension::GetExtensionVersion(HSE_VERSION_INFO* pVer)
  45. {
  46.     // Call default implementation for initialization
  47.     CHttpServer::GetExtensionVersion(pVer);
  48.  
  49.     // Load description string
  50.     TCHAR sz[HSE_MAX_EXT_DLL_NAME_LEN+1];
  51.     ISAPIVERIFY(::LoadString(AfxGetResourceHandle(),
  52.             IDS_SERVER, sz, HSE_MAX_EXT_DLL_NAME_LEN));
  53.     _tcscpy(pVer->lpszExtensionDesc, sz);
  54.     return TRUE;
  55. }
  56.  
  57. ///////////////////////////////////////////////////////////////////////
  58. // CEchoExtension command handlers
  59.  
  60. //Lab 10.2, ex 2 - Implementing Echo
  61. void CEchoExtension::Default(CHttpServerContext* pCtxt)
  62. {
  63.     StartContent(pCtxt);
  64.     WriteTitle(pCtxt);
  65.  
  66.     *pCtxt << "<P><H1>Help for Echo.dll</H1><P><HR>";
  67.     *pCtxt << "You have called the Echo ISAPI application without supplying "
  68.            << "a method and an argument.";
  69.     EchoHelp(pCtxt);
  70.     *pCtxt << "\r\n";
  71.  
  72.     EndContent(pCtxt);
  73. }
  74.  
  75.  
  76. //Lab 10.2, ex 2 - Implementing Echo
  77. void CEchoExtension::EchoRequest(CHttpServerContext* pCtxt, LPCTSTR pstrOption)
  78. {
  79.     pCtxt->m_pECB->dwHttpStatusCode = 200;
  80.     StartContent(pCtxt);
  81.     WriteTitle(pCtxt);
  82.  
  83.     *pCtxt << "<P><H1>Echo.dll</H1><P><HR>";
  84.  
  85.     if ( _stricmp(pstrOption, "full") == 0)
  86.     {
  87.         EchoHead(pCtxt);
  88.         *pCtxt << "<BR>";
  89.         EchoBody(pCtxt);
  90.     }
  91.     else if ( _stricmp(pstrOption, "header") == 0)
  92.     {
  93.         EchoHead(pCtxt);
  94.     }
  95.     else if ( _stricmp(pstrOption, "body") == 0)
  96.     {
  97.         EchoBody(pCtxt);
  98.     }
  99.     else
  100.         BadSyntax(pCtxt);
  101.  
  102.     EndContent(pCtxt);
  103. }
  104.  
  105. ///////////////////////////////////////////////////////////////////////
  106. // Implementation member functions
  107. //Lab 10.2, ex 2 - Implementing Echo
  108.  
  109. void CEchoExtension::EchoBody(CHttpServerContext* pCtxt)
  110. {
  111.     *pCtxt << "<P><H3>Request Body Information</H3><BR>";
  112.  
  113.     DWORD dwContentLength = pCtxt->m_pECB->cbTotalBytes;
  114.     //If there is no HTTP body, then don't process.
  115.     if ( dwContentLength == 0)
  116.     {
  117.         *pCtxt << "<I>No Request Body Present.</I>";
  118.         return;
  119.     }
  120.  
  121.     //Else, allocate stack buffer, read in, then write out.
  122.     char pstrBuffer[4000];
  123.     DWORD dwSize = sizeof(pstrBuffer);
  124.     BOOL b = pCtxt->ReadClient(pstrBuffer, &dwSize);
  125.     if (b == TRUE)
  126.     {
  127.         *pCtxt << "<I>Request Body, First " << (long int)dwSize
  128.                << " of " << (long int)dwContentLength 
  129.                << " Total Bytes Follows:</I> <BR>";
  130.         *pCtxt << pstrBuffer;
  131.     }
  132.     else  //report error back and set status code
  133.     {
  134.         *pCtxt << "<I>Error in Reading Request Body!</I>";
  135.         pCtxt->m_pECB->dwHttpStatusCode = 500;
  136.     }
  137. }
  138.  
  139. //EchoHead actually picks off the typical information from the
  140. //HTTP header after it is parsed by the Web server; it is not a
  141. //true echo.
  142. void CEchoExtension::EchoHead(CHttpServerContext* pCtxt)
  143. {
  144.     char pstrBuffer[1000];
  145.     DWORD dwSize = sizeof(pstrBuffer);
  146.     #define MECB  pCtxt->m_pECB
  147.  
  148.     *pCtxt << "<P><H3>Request Header Information</H3>";
  149.     *pCtxt << "<BR>Request method: " << MECB->lpszMethod;
  150.     *pCtxt << "<BR>Tranlsated path: " << MECB->lpszPathTranslated;
  151.     
  152.     dwSize = sizeof(pstrBuffer); pstrBuffer[0] = 0;
  153.     pCtxt->GetServerVariable("QUERY_STRING", pstrBuffer, &dwSize);
  154.     *pCtxt << "<BR>Query String: " << pstrBuffer;
  155.  
  156.     dwSize = sizeof(pstrBuffer); pstrBuffer[0] = 0;
  157.     pCtxt->GetServerVariable("REMOTE_USER", pstrBuffer, &dwSize);
  158.     *pCtxt << "<P>Client User name: " 
  159.            << (pstrBuffer[0]==0?"Anonymous":pstrBuffer);
  160.  
  161.     dwSize = sizeof(pstrBuffer); pstrBuffer[0] = 0;
  162.     pCtxt->GetServerVariable("REMOTE_HOST", pstrBuffer, &dwSize);
  163.     *pCtxt << "<BR>Client host name: " << pstrBuffer;
  164.  
  165.     dwSize = sizeof(pstrBuffer); pstrBuffer[0] = 0;
  166.     pCtxt->GetServerVariable("REMOTE_ADDR", pstrBuffer, &dwSize);
  167.     *pCtxt << "<BR>Client IP address: " << pstrBuffer;
  168.  
  169.     dwSize = sizeof(pstrBuffer); pstrBuffer[0] = 0;
  170.     pCtxt->GetServerVariable("HTTP_ACCEPT", pstrBuffer, &dwSize);
  171.     *pCtxt << "<P>Accept fields: " << pstrBuffer;
  172.  
  173.     dwSize = sizeof(pstrBuffer); pstrBuffer[0] = 0;
  174.     pCtxt->GetServerVariable("CONTENT_TYPE", pstrBuffer, &dwSize);
  175.     *pCtxt << "<BR>Content type (POST): " << pstrBuffer;
  176.  
  177.     dwSize = sizeof(pstrBuffer); pstrBuffer[0] = 0;
  178.     pCtxt->GetServerVariable("CONTENT_LENGTH", pstrBuffer, &dwSize);
  179.     *pCtxt << "<BR>Content length: " << pstrBuffer;
  180.  
  181.     *pCtxt << "<P><B>Gratuitous Server Information</B>";
  182.  
  183.     dwSize = sizeof(pstrBuffer); pstrBuffer[0] = 0;
  184.     pCtxt->GetServerVariable("SERVER_PROTOCOL", pstrBuffer, &dwSize);
  185.     *pCtxt << "<BR>Service protocol: " << pstrBuffer;
  186.  
  187.     dwSize = sizeof(pstrBuffer); pstrBuffer[0] = 0;
  188.     pCtxt->GetServerVariable("SERVER_NAME", pstrBuffer, &dwSize);
  189.     *pCtxt << "<BR>Server Name: " << pstrBuffer;
  190.  
  191.     dwSize = sizeof(pstrBuffer); pstrBuffer[0] = 0;
  192.     pCtxt->GetServerVariable("SERVER_SOFTWARE", pstrBuffer, &dwSize);
  193.     *pCtxt << "<BR>Server Software: " << pstrBuffer;
  194.  
  195.     dwSize = sizeof(pstrBuffer); pstrBuffer[0] = 0;
  196.     *pCtxt << "<P>";
  197.  
  198.     #undef MECB  //pCtxt->m_pECB
  199. }
  200.  
  201. void CEchoExtension::BadSyntax(CHttpServerContext* pCtxt)
  202. {
  203.     *pCtxt << "<H3>Bad Syntax Error!</H3><P>";
  204.     *pCtxt << "You have called the Echo ISAPI application without supplying "
  205.            << "the proper argument. You must specify a method and a single" 
  206.            << " argument.";
  207.     EchoHelp(pCtxt);
  208. }
  209.  
  210. void CEchoExtension::EchoHelp(CHttpServerContext* pCtxt)
  211. {
  212.     *pCtxt << "<P><I>Supported method:</I>";
  213.     *pCtxt << "<BR><B><TT>EchoRequest</TT></B> - currently the only method supported."
  214.            << " Dynamically creates an HTML page containing HTTP request information.";
  215.     *pCtxt << "<P><I>Supported arguments:</I>";
  216.     *pCtxt << "<BR><B><TT>Full</TT></B> - echo back the entire HTTP request message.";
  217.     *pCtxt << "<BR><B><TT>Body</TT></B> - echo back only the HTTP request message body.";
  218.     *pCtxt << "<BR><B><TT>Header</TT></B> - echo back only the HTTP request message head.";
  219.     *pCtxt << "<P>For example, if you have installed Echo.dll on the server \"WebSvr\"" 
  220.            << "then the following URL would display information on the HTTP request "
  221.            << "message header and body:";
  222.     *pCtxt << "<BR><B><TT>http://WebSvr/Scripts/Echo.dll?EchoRequest&Full</TT></B>";
  223. }
  224. ///////////////////////////////////////////////////////////////////////
  225. // If your extension will not use MFC... [remainder deleted]
  226.